package com.hyt.it.ogt.kq.main.controller.bm;

import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.hyt.common.apiInfor.ApiResponse;
import com.hyt.core.util.FastJsonUtil;
import com.hyt.it.ogt.kq.common.bm.enums.pay.nonTaxPay.BsBase64Util;
import com.hyt.it.ogt.kq.common.bm.enums.pay.nonTaxPay.CharType;
import com.hyt.it.ogt.kq.common.bm.enums.pay.nonTaxPay.RSASignUtil;
import com.hyt.it.ogt.kq.common.bm.utils.Constant;
import com.hyt.it.ogt.kq.main.controller.base.BaseController;
import com.hyt.it.ogt.kq.service.bm.model.entity.StudentPayInfo;
import com.hyt.it.ogt.kq.service.bm.model.entity.StudentSubject;
import com.hyt.it.ogt.kq.service.bm.model.vo.OrderInfoVo;
import com.hyt.it.ogt.kq.service.bm.model.vo.PayVo;
import com.hyt.it.ogt.kq.service.bm.model.vo.ProjectOrderFlowVo;
import com.hyt.it.ogt.kq.service.bm.pay.NcNonTaxPayCallBackData;
import com.hyt.it.ogt.kq.service.bm.pay.NcNonTaxPayCallBackParams;
import com.hyt.it.ogt.kq.service.bm.pay.NcNonTaxPayCallBackResult;
import com.hyt.it.ogt.kq.service.bm.service.IPayOrderService;
import com.hyt.it.ogt.kq.service.bm.service.IStudentPayService;
import com.hyt.log.annotation.Log;
import com.hyt.model.PageParam;
import com.hyt.model.tps.entity.PeePayNotify;

import cn.hutool.core.util.StrUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiOperationSort;
import io.swagger.annotations.ApiSort;
import lombok.extern.slf4j.Slf4j;

/**
 * 
 * @author wangt
 * @Description:
 * @date: 2020年9月1日 下午4:11:46
 * @version: V1.0
 */
@RestController
@Api(tags = "18.考生端：支付相关接口", value = "考生支付相关接口")
@ApiSort(value = 18)
@Slf4j
@RequestMapping("/bm/studentPay")
public class StudentPayController extends BaseController {

	@Autowired
	private IStudentPayService iStudentPayService;

	@Autowired
	IPayOrderService iPayOrderService;
	
	
	
	/**
	 * 去支付：查询缴费信息
	 * 
	 * @param
	 * @param
	 * @return
	 */
	@ApiOperation(value = "18.1.1 去支付：查询缴费信息", notes = "20000:成功")
	@ApiOperationSort(value = 1)
	@RequestMapping(value = "/queryPayInfo", method = RequestMethod.GET)
	public ApiResponse<Object> queryPayInfo(String studentId) {
		Map<String, Object> map  = iStudentPayService.queryPayInfo(studentId);
		if ("15038".equals(map.get("code"))) {
			return ApiResponse.builder().code(Constant.RESPONSE_CODE_31010172).data("考生60秒内重复缴费，请勿重新提交！").build();
		}
		if ("15046".equals(map.get("code"))) {
			return ApiResponse.builder().code(Constant.RESPONSE_CODE_31010173).data("该项目设置不需要缴费！").build();
		}
		if ("15044".equals(map.get("code"))) {
			return ApiResponse.builder().code(Constant.RESPONSE_CODE_31010174).data("考生暂无需缴费科目，请勿重复缴费！").build();
		}
		if ("15048".equals(map.get("code"))) {
			return ApiResponse.builder().code(Constant.RESPONSE_CODE_31010175).data("您报名的科目暂未通过审核，请等待通过审核再进行缴费！").build();
		}
		if (map.get("code").equals(Constant.RESPONSE_CODE_31010112)) {
			return ApiResponse.builder().code(Constant.RESPONSE_CODE_31010112).data("报名时间已过，无法缴费！").build();
		}
		StudentPayInfo studentPayInfo = (StudentPayInfo) map.get("studentPayInfo");
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data(studentPayInfo).build();
	}

	/**
	 * 去支付：跳转第三方支付页面进行支付
	 * 
	 * @param
	 * @param
	 * @return
	 */
	@ApiOperation(value = "18.1.2 去支付：跳转第三方支付页面进行支付(国内支付)", notes = "20000:成功")
	@ApiOperationSort(value = 2)
	@Log(module = "考生支付管理", business = "考生去支付")
	@RequestMapping(value = "/pay", method = RequestMethod.POST)
	public ApiResponse<Object> pay(@RequestBody PayVo payVo) {
		log.info("## pay payVo:{}", FastJsonUtil.getBeanToJson(payVo));
		Map<String, Object> payMap = iStudentPayService.pay(payVo);
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data(payMap).build();
	}


	/**
	 * 微信支付接口：跳转第三方支付页面进行支付
	 *
	 * @param
	 * @param
	 * @return
	 */

	@ApiOperation(value = "18.1.9 微信支付接口：跳转第三方支付页面进行支付(国内支付)", notes = "20000:成功")
	@ApiOperationSort(value = 9)
	@Log(module = "考生支付管理", business = "考生微信小程序去支付")
	@RequestMapping(value = "/payWechat", method = RequestMethod.POST)
	public ApiResponse<Object> payWechat(@RequestBody PayVo payVo,HttpServletRequest request) {
	    log.info("# payWechat payVo:{}", FastJsonUtil.getBeanToJson(payVo));
		Map<String, Object> payMap = iStudentPayService.payWeChat(payVo,request);
		log.info("# payWechat payMap:{}", FastJsonUtil.getBeanToJson(payMap));
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data(payMap).build();
	}


	/**
	 * 去支付：跳转第三方支付页面进行支付
	 * 
	 * @param
	 * @param
	 * @return
	 * @throws IOException
	 */
	@ApiOperation(value = "18.1.3  去支付：第三方回调地址（后台回调用）", notes = "20000:成功")
	@ApiOperationSort(value = 3)
	@RequestMapping(value = "/notifyUrl", method = RequestMethod.POST)
	public Object notifyUrl(HttpServletRequest req, HttpServletResponse resp, String officeId) throws Exception {
		log.info("-----------------notifyUrl POST--------------------");
		Map<String, Object> payMap = iStudentPayService.notifyUrl(req, officeId);
		log.info("-----------------notifyUrl POST result:{}--------------------", JSON.toJSON(payMap));
		//return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data(payMap).build();
		return "SUCCESS";
	}
	
	@ApiOperation(value = "18.1.3  去支付：第三方回调地址（后台回调用）", notes = "14001:成功")
	@ApiOperationSort(value = 3)
	@RequestMapping(value = "/notifyUrl", method = RequestMethod.GET)
	public Object notifyUrlNew(PeePayNotify peePayNotify,HttpServletRequest request) throws IOException {
		log.info("notifyUrl get  peePayNotify:[{}],queryStr:[{}] " ,  JSON.toJSON(peePayNotify), request.getQueryString());
		String queryString = request.getQueryString();
		Map<String,String> queryMap = new HashMap<>();
		if(StringUtils.isNotEmpty(queryString)) {
			String[] queryStrArry = queryString.split("&");
			if(null != queryStrArry && queryStrArry.length > 0) {
				for (int i = 0; i < queryStrArry.length; i++) {
					String[] splitStrArry = queryStrArry[i].split("=");
					if(null != splitStrArry && splitStrArry.length > 1) {
						queryMap.put(splitStrArry[0], splitStrArry[1]);
					}
				}
			}
		}
		log.info("notifyUrl get  peePayNotify:[{}],queryMap:[{}] " ,  JSON.toJSON(peePayNotify), JSON.toJSON(queryMap));

		Map<String, Object> payMap = iStudentPayService.notifyUrl(peePayNotify, queryMap);
		log.info("notifyUrl post result:[{}]" ,  JSON.toJSON(payMap));
		return "SUCCESS";
	}

	/**
	 * 去支付：国际支付
	 * 
	 * @param
	 * @param
	 * @return
	 */
	@ApiOperation(value = "18.1.4  去支付：跳转第三方支付页面进行支付(国际支付)", notes = "20000:成功")
	@ApiOperationSort(value = 4)
	@RequestMapping(value = "/payNation", method = RequestMethod.POST)
	public ApiResponse<Object> payNation(@RequestBody PayVo payVo) {
		//Map<String, Object> payMap = iStudentPayService.pay(payVo);
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data("").build();
	}
	
	/**
	 *  考生端：订单管理列表
	 * 
	 * @param
	 * @param
	 * @return
	 */
	@ApiOperation(value = "18.1.5  考生端：订单管理列表", notes = "20000:成功")
	@ApiOperationSort(value = 5)
	@RequestMapping(value = "/orderList", method = RequestMethod.GET)
	public ApiResponse<Object> orderList(String payStatus,String regId,PageParam<OrderInfoVo> pageParam) {
		IPage<OrderInfoVo> page = pageParam;
		page = iStudentPayService.orderList(pageParam,payStatus,regId);
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data(page).build();
	}

	@ApiOperation(value = "18.1.6 考生端： 订单管理列表- 查询订单详情", notes = "20000:成功")
	@ApiOperationSort(value = 6)
	@RequestMapping(value = "/queryOrderInfo", method = RequestMethod.GET)
	public ApiResponse<Object> queryOrderInfo(String orderId) {
		OrderInfoVo object = iPayOrderService.queryOrderInfo(orderId);
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data(object).build();
	}
	
	@ApiOperation(value = "18.1.7 考生端：订单列表- 查询科目列表-退款", notes = "20000:成功")
	@ApiOperationSort(value = 7)
	@RequestMapping(value = "/refundSubjectList", method = RequestMethod.GET)
	public ApiResponse<Object> refundSubjectList(String orderId) {
		List<StudentSubject> studentSubject = iPayOrderService.refundSubjectList(orderId);
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data(studentSubject).build();
	}

	@ApiOperation(value = "18.1.8  考生端：申请 退款", notes = "20000:成功,31181801:不存在需要退款的科目, 31181802:退费截止时间已过, 31181803:已申请退款，请勿重复提交")
	@ApiOperationSort(value = 8)
	@Log(module = "考生支付管理", business = "考生申请退款")
	@RequestMapping(value = "/applyForRefund", method = RequestMethod.GET)
	public ApiResponse<Object> applyForRefund(String orderId, String subjectIds,String regId,String projectId) {
		int code = iPayOrderService.applyForRefund(orderId, subjectIds, regId, projectId);
		if (code == 31181803) {
			return ApiResponse.builder().code(31181803).data("已申请退款，请勿重复提交！").build();
		} else if (code == 31181802) {
			return ApiResponse.builder().code(31181802).data("退费截止时间已过!").build();
		} else if (code == 31181801) {
			return ApiResponse.builder().code(31181801).data("不存在需要退款的科目!").build();
		}
		return ApiResponse.builder().code(Constant.RESPONSE_CODE_SUCCESS).data("申请退款成功！").build();
	}
	
	
	
	@ApiOperation(value = "18.1.8.1  考生端：申请 按照科目退款", notes = "20000:成功,31181811:不存在需要退款的科目, 31181812:退费截止时间已过, 31181813:已申请退款，请勿重复提交")
	@ApiOperationSort(value = 8)
	@Log(module = "考生支付管理", business = "按照科目申请退款")
	@RequestMapping(value = "/applyForRefundBySubjects", method = RequestMethod.GET)
	public ApiResponse<String> applyForRefundBySubjects(String subjectIds, String regId, String projectId) {
	    int code = iPayOrderService.applyForRefundBySubjects(subjectIds, regId, projectId);
        if (code == 31181804) {
            return ApiResponse.<String> builder().code(31181804).data("项目不允许退费").build();
        }else if (code == 31181803) {
            return ApiResponse.<String> builder().code(31181803).data("已申请退款，请勿重复提交！").build();
        } else if (code == 31181802) {
            return ApiResponse.<String> builder().code(31181802).data("退费截止时间已过!").build();
        } else if (code == 31181801) {
            return ApiResponse.<String> builder().code(31181801).data("不存在需要退款的科目!").build();
        }
        return ApiResponse.<String> builder().code(Constant.RESPONSE_CODE_SUCCESS).data("申请退款成功！").build();
    }


	
	
	@ApiImplicitParams({
		@ApiImplicitParam(
			name = "projectId", value = "项目id", dataType = "string", paramType = "query", required = true
		),
		@ApiImplicitParam(
			name = "regId", value = "考生用户id", dataType = "string", paramType = "query", required = true
		)
	})
	@ApiOperation(value = "18.1.9  考生端：查询项目订单列表", notes = "20000:成功,31181811:不存在需要退款的科目, 31181812:退费截止时间已过, 31181813:已申请退款，请勿重复提交")
	@ApiOperationSort(value = 8)
	@RequestMapping(value = "/queryProjectOrderFlowList", method = RequestMethod.GET)
	public ApiResponse<List<ProjectOrderFlowVo>> queryProjectOrderFlowList(String projectId, String regId) {
		List<ProjectOrderFlowVo> projectOrderFlowVos = iPayOrderService.queryProjectOrderFlowList(projectId, regId);
		return ApiResponse.<List<ProjectOrderFlowVo>>builder().code(Constant.RESPONSE_CODE_SUCCESS).data(projectOrderFlowVos).build();
	}
	
	
	@ApiOperation(value = "18.2.1  易宝支付回调：第三方回调地址（后台回调用）", notes = "20000:成功")
	@ApiOperationSort(value = 3)
	@RequestMapping(value = "/yopnotifyUrl", method = RequestMethod.POST, produces = "text/plain")
	public Object poynotifyUrl(HttpServletRequest req,HttpServletResponse resp) throws Exception {
		String response = req.getParameter("response");
		log.info("## poynotifyUrl response:[{}]" ,  response);
        String customerIdentification = req.getParameter("customerIdentification");
        String officeId = req.getParameter("officeId");
        log.info("## poynotifyUrl customerIdentification:[{}]" ,  customerIdentification);
        String orderJson = iPayOrderService.analysisYopNotifyStr(response, officeId);
        log.info("## poynotifyUrl orderJson:[{}]" ,  orderJson);
        if(StrUtil.isBlankIfStr(orderJson)) {
            return "FAIL";
        }
        Map<String, Object> payMap = iStudentPayService.poynotifyUrl(customerIdentification, orderJson);
		log.info("## poynotifyUrl post result:[{}]" ,  JSON.toJSON(payMap));
		return "SUCCESS";
	}
	
	@ApiOperation(value = "18.2.2  易宝支付回调：第三方回调地址（后台回调用）", notes = "20000:成功")
	@ApiOperationSort(value = 3)
	@RequestMapping(value = "/yopnotifyUrl", method = RequestMethod.GET, produces = "text/plain")
	public Object poynotifyUrlGet(HttpServletRequest req,HttpServletResponse resp) throws Exception {
		String response = req.getParameter("response");
		log.info("## poynotifyUrl response:[{}]" ,  response);
        String customerIdentification = req.getParameter("customerIdentification");
        String officeId = req.getParameter("officeId");
        log.info("## poynotifyUrl customerIdentification:[{}]" ,  customerIdentification);
        String orderJson = iPayOrderService.analysisYopNotifyStr(response, officeId);
        log.info("## poynotifyUrl orderJson:[{}]" ,  orderJson);
        if(StrUtil.isBlankIfStr(orderJson)) {
            return "FAIL";
        }
		return "SUCCESS";
	}
	
    @ApiOperation(value = "18.3.1  南昌非税支付回调：第三方回调地址（后台回调用）", notes = "20000:成功")
    @ApiOperationSort(value = 3)
    @RequestMapping(value = "/ncNonTaxPayNotifyUrl", method = RequestMethod.POST, produces = "text/plain")
    public Object ncNonTaxPayNotifyUrl(HttpServletRequest req, HttpServletResponse resp, @RequestParam Map<String, Object> params ) throws Exception {
        log.info("## ncNonTaxPayNotifyUrl params:{}", FastJsonUtil.getBeanToJson(params));
        String reqdata = (String) params.get("reqData");
        String merapp = (String) params.get("merapp");
        log.info("## ncNonTaxPayNotifyUrl reqdata:{},merapp:{}", reqdata, merapp);
        String reqDataBase64Str = BsBase64Util.decodeBase64String(reqdata, CharType.UTF8);
        NcNonTaxPayCallBackParams ncNonTaxPayCallBackParams = FastJsonUtil.getJsonToBean(reqDataBase64Str, NcNonTaxPayCallBackParams.class);
        log.info("## ncNonTaxPayNotifyUrl ncNonTaxPayCallBackParams:{}", FastJsonUtil.getBeanToJson(ncNonTaxPayCallBackParams));
        String ordNo = ncNonTaxPayCallBackParams.getOrdNo();
        String tranStatus = ncNonTaxPayCallBackParams.getTranStatus();
        String officeId = req.getParameter("officeId");
        log.info("## ncNonTaxPayNotifyUrl officeId:{}, ordNo:{}, tranStatus:{}", officeId, ordNo, tranStatus);
        if (StrUtil.isBlankIfStr(ordNo) || StrUtil.isBlankIfStr(officeId) || StrUtil.isBlankIfStr(tranStatus) || !"1".equals(tranStatus)) {
            NcNonTaxPayCallBackData ncNonTaxPayCallBackData = new NcNonTaxPayCallBackData(ordNo, "0");
            String respData = FastJsonUtil.getBeanToJson(ncNonTaxPayCallBackData);
            // 创建签名
            Map<String, String> signParam = new HashMap<>();
            signParam.put("respCode", NcNonTaxPayCallBackResult.respcode_fail);
            signParam.put("respData", respData);
            //使用私钥对摘要进行数字签名
            String sign = RSASignUtil.newRSASign(signParam, iPayOrderService.getNcNonTaxPayPrivateKey(officeId));
            return FastJsonUtil.getBeanToJson(new NcNonTaxPayCallBackResult(NcNonTaxPayCallBackResult.respcode_fail, respData, sign, CharType.UTF8.value));
        }
        try {
            NcNonTaxPayCallBackData ncNonTaxPayCallBackData= iStudentPayService.ncNonTaxPayNotify(merapp, ordNo, officeId, ncNonTaxPayCallBackParams);
            log.info("## ncNonTaxPayNotifyUrl post result:[{}]", JSON.toJSON(ncNonTaxPayCallBackData));
            if(NcNonTaxPayCallBackData.oprStatus_success.equals(ncNonTaxPayCallBackData.getOprStatus())) {
                String respData = FastJsonUtil.getBeanToJson(ncNonTaxPayCallBackData);
                // 创建签名
                Map<String, String> signParam = new HashMap<>();
                signParam.put("respCode", NcNonTaxPayCallBackResult.respcode_success);
                signParam.put("respData", respData);
                //使用私钥对摘要进行数字签名
                String sign = RSASignUtil.newRSASign(signParam, iPayOrderService.getNcNonTaxPayPrivateKey(officeId));
                return FastJsonUtil.getBeanToJson(new NcNonTaxPayCallBackResult(NcNonTaxPayCallBackResult.respcode_success, respData, sign, CharType.UTF8.value));
            }else {
                String respData = FastJsonUtil.getBeanToJson(ncNonTaxPayCallBackData);
                // 创建签名
                Map<String, String> signParam = new HashMap<>();
                signParam.put("respCode", NcNonTaxPayCallBackResult.respcode_fail);
                signParam.put("respData", respData);
                //使用私钥对摘要进行数字签名
                String sign = RSASignUtil.newRSASign(signParam, iPayOrderService.getNcNonTaxPayPrivateKey(officeId));
                return FastJsonUtil.getBeanToJson(new NcNonTaxPayCallBackResult(NcNonTaxPayCallBackResult.respcode_fail, respData, sign, CharType.UTF8.value));
            }
        } catch (Exception e) {
            NcNonTaxPayCallBackData ncNonTaxPayCallBackData = new NcNonTaxPayCallBackData(ordNo, NcNonTaxPayCallBackData.oprStatus_fail);
            String respData = FastJsonUtil.getBeanToJson(ncNonTaxPayCallBackData);
            // 创建签名
            Map<String, String> signParam = new HashMap<>();
            signParam.put("respCode", NcNonTaxPayCallBackResult.respcode_fail);
            signParam.put("respData", respData);
            //使用私钥对摘要进行数字签名
            String sign = RSASignUtil.newRSASign(signParam, iPayOrderService.getNcNonTaxPayPrivateKey(officeId));
            return FastJsonUtil.getBeanToJson(new NcNonTaxPayCallBackResult(NcNonTaxPayCallBackResult.respcode_fail, respData, sign, CharType.UTF8.value));
        }
    }
}
